from entity.tool import getTerm

# 定义Grammar类
# __init__(self, left, right, pos=0): 构造函数，用于创建一个Grammar对象
# 属性：
# left表示文法的左部，right表示文法的右部，pos表示当前读入到右部的第几个符号（默认值为0）
# 方法：
# getLeft(self): 返回文法的左部
# getRight(self): 返回文法的右部
# getCurDire(self): 返回当前读入的符号
# isReg(self): 判断是否可以进行规约操作
# forward(self): 将当前读入的符号向前移动一位
# __str__(self): 返回该文法的字符串表示
# copy(self): 返回该文法的副本
# __hash__(self): 返回该文法的哈希值
# __eq__(self, other): 判断该文法是否与另一个文法相等
# getOriGram(self): 返回该文法的原始文法，即pos为0的文法
# 该类还定义了一些辅助函数，例如getTerm函数（未提供代码），用于从右部中获取一个终结符
class Grammar:
    # 给出文法左部和右部，生成文法对象
    def __init__(self, left, right, pos=0):
        self._left = left
        self._oriRight = right
        syms = []
        # 首先需要切割右部，分成若干个终结符和非终结符
        while True:
            if right is None or len(right) == 0:
                break
            if right[0] == '<':  # 如果是一个非终结符
                endPos = right.find('>')  # 找到截止位置
                syms.append(right[:endPos + 1])  # 添加这个非终结符
                right = right[endPos + 1:]  # 剪断
            else:  # 如果是一个非终结符
                ter = getTerm(right)
                right = right[len(ter):]
                syms.append(ter)
        # 设置右侧项目表
        self._right = syms
        # 当前的位置为0
        self._pos = pos

    # 得到左部
    def getLeft(self):
        return self._left

    # 得到右部
    def getRight(self):
        return self._right

    # 得到当前方向
    def getCurDire(self):
        # 如果已经可以规约了
        if self._pos == len(self._right):
            return None
        return self._right[self._pos]

    # 是否可以规约
    def isReg(self):
        return self.getCurDire() is None

    # 前进一格
    def forward(self):
        if self._pos < len(self._right):
            self._pos += 1

    # 转换成字符串
    def __str__(self):
        lastFlag = True
        res = str(self._left) + '->'
        for i in range(len(self._right)):

            if i == self._pos:
                res += '!'
                lastFlag = False
            res += self._right[i]
        if lastFlag:
            res += '!'
        return res

    # 获得一个数据拷贝
    def copy(self):
        return Grammar(self._left, self._oriRight, self._pos)

    def __hash__(self):
        return hash(str(self))

    def __eq__(self, other):
        if self._left == other._left and self._oriRight == other._oriRight and self._pos == other._pos:
            return True
        return False

    # 得到位置为0的原始文法
    def getOriGram(self):
        return Grammar(self._left, self._oriRight, 0);
